package indigo.context
{
	import indigo.config.IObjectDefinition;
	import indigo.events.FactoryEvent;
	import indigo.factory.IObjectFactory;
	import indigo.factory.SimpleObjectFactory;
	import indigo.register.IObjectDefinitionRegistry;
	
	public class XmlApplicationContext implements IApplicationContext {
		private var _factory:IObjectFactory;
		private var _name:String;
		
		/**
		 * Create an <code>ApplicationContext</code> object
		 * Creer un objet <code>ApplicationContext</code>
		 * 
		 * @param name
		 * @param registry
		 * 
		 */
		public function XmlApplicationContext(name:String, registry:IObjectDefinitionRegistry) {
			_name = name;
			_factory = new SimpleObjectFactory(registry);
			preInstanciedSingletons();
		}

		/**
		 * Get the reference to the repository of objects
		 * Obtenir la reference au referentiel d'objets.
		 * 
		 * @return 
		 * 
		 */
		public function get register():IObjectDefinitionRegistry
		{
			return _factory.register;
		}
		
		/**
		 * Get the name to the application context
		 * Obtenir le nom du context applicatif
		 * @return 
		 * 
		 */
		public function get name():String
		{
			return _name;
		}
		
		/**
		 * Definit le nom du context applicatif, vous ne serez jamais amener
		 * a le definir vous même, l'objet <code>ContextManager</code> s'en charge.
		 * @param value
		 * 
		 * @see ContextManager
		 */
		public function set name(value:String):void
		{
			_name = value;
		}
		
		/**
		 * Obtenir a partir du nom d'identification de definition
		 * une instance de l'objet correspondant.
		 * 
		 * @param name	Nom d'identification de la definition.
		 * @return 
		 * 
		 * @see indigo.factory.IObjectFactory
		 */
		public function getObject(name:String):Object
		{
			return _factory.getObject(name);
		}
		
		public function toString():String {
			return name;
		}
		
		protected function preInstanciedSingletons():void {
			// TODO: that's SimpleObjectFactory to manage singletons
			var definitions:Array = register.getDefinitionNames();
			var definition:IObjectDefinition;
			for each(var nameDef:String in definitions) {
				definition = register.getDefinition(nameDef);
				if(definition.isSingleton)
					getObject(nameDef);
			}
		}
	}
}